package com.warom.sdg.service;

import android.content.Context;
import android.util.Log;
import android.webkit.JavascriptInterface;

import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;
import com.warom.sdg.dao.OperationLogDao;
import com.warom.sdg.database.SdgDatabase;
import com.warom.sdg.dto.OperationLogDto;
import com.warom.sdg.dto.PageResponseDto;
import com.warom.sdg.model.ApiResponse;
import com.warom.sdg.model.OperationLogEntity;

import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

/**
 * 操作日志服务类
 * 提供操作日志的记录和查询功能
 */
public class OperationLogService {
    private static final String TAG = "OperationLogService";
    
    private final Context context;
    private final OperationLogDao operationLogDao;
    private final ExecutorService executor;
    private final Gson gson;
    private final SimpleDateFormat dateFormat;
    
    public OperationLogService(Context context) {
        this.context = context;
        this.operationLogDao = SdgDatabase.getInstance(context).getOperationLogDao();
        this.executor = Executors.newFixedThreadPool(2);
        this.gson = new Gson();
        this.dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss", Locale.getDefault());
    }
    
    /**
     * 记录操作日志
     * @param username 用户名
     * @param operationType 操作类型
     * @param operationDescription 操作描述
     * @param operationPage 操作页面
     * @param operationTarget 操作目标
     * @param operationStatus 操作状态
     * @param errorMessage 错误信息（可选）
     */
    @JavascriptInterface
    public void logOperation(String username, String operationType, String operationDescription,
                           String operationPage, String operationTarget, String operationStatus,
                           String errorMessage) {
        executor.execute(() -> {
            try {
                OperationLogEntity log = new OperationLogEntity();
                log.setUsername(username);
                log.setOperationType(operationType);
                log.setOperationDescription(operationDescription);
                log.setOperationPage(operationPage);
                log.setOperationTarget(operationTarget);
                log.setOperationStatus(operationStatus);
                log.setErrorMessage(errorMessage);
                log.setOperationTime(System.currentTimeMillis());
                log.setOperationTimeString(dateFormat.format(new Date()));
                
                long id = operationLogDao.insert(log);
                Log.d(TAG, "操作日志记录成功，ID: " + id + ", 操作: " + operationDescription);
            } catch (Exception e) {
                Log.e(TAG, "记录操作日志失败: " + e.getMessage(), e);
            }
        });
    }
    
    /**
     * 从JSON参数记录操作日志
     * @param args JSON格式的参数字符串
     * @return 操作结果
     */
    @JavascriptInterface
    public String logOperation(String args) {
        try {
            Map<String, String> params = gson.fromJson(args, new TypeToken<Map<String, String>>(){}.getType());
            
            String username = params.get("username");
            String operationType = params.get("operationType");
            String operationDescription = params.get("operationDescription");
            String operationPage = params.get("operationPage");
            String operationTarget = params.get("operationTarget");
            String operationStatus = params.get("operationStatus");
            String errorMessage = params.get("errorMessage");
            
            logOperation(username, operationType, operationDescription, operationPage, 
                        operationTarget, operationStatus, errorMessage);
            
            // 使用ApiResponse返回成功结果
            ApiResponse<String> response = ApiResponse.success("操作日志记录成功");
            return gson.toJson(response);
        } catch (Exception e) {
            Log.e(TAG, "解析操作日志参数失败: " + e.getMessage(), e);
            // 使用ApiResponse返回错误结果
            ApiResponse<String> errorResponse = ApiResponse.error("记录操作日志失败: " + e.getMessage());
            return gson.toJson(errorResponse);
        }
    }
    
    /**
     * 记录设备控制操作
     * @param username 用户名
     * @param deviceName 设备名称
     * @param action 操作动作（开启/关闭）
     * @param status 操作状态
     * @param errorMessage 错误信息
     */
    @JavascriptInterface
    public void logDeviceControl(String username, String deviceName, String action, 
                               String status, String errorMessage) {
        String description = String.format("%s%s", action, deviceName);
        logOperation(username, OperationLogEntity.OperationType.DEVICE_CONTROL, 
                    description, "智能通风系统", deviceName, status, errorMessage);
    }
    
    /**
     * 从JSON参数记录设备控制操作
     * @param args JSON格式的参数字符串
     * @return 操作结果
     */
    @JavascriptInterface
    public String logDeviceControl(String args) {
        try {
            Map<String, String> params = gson.fromJson(args, new TypeToken<Map<String, String>>(){}.getType());
            
            String username = params.get("username");
            String deviceName = params.get("deviceName");
            String action = params.get("action");
            String status = params.get("status");
            String errorMessage = params.get("errorMessage");
            
            logDeviceControl(username, deviceName, action, status, errorMessage);
            
            // 使用ApiResponse返回成功结果
            ApiResponse<String> response = ApiResponse.success("设备控制操作日志记录成功");
            return gson.toJson(response);
        } catch (Exception e) {
            Log.e(TAG, "解析设备控制操作日志参数失败: " + e.getMessage(), e);
            // 使用ApiResponse返回错误结果
            ApiResponse<String> errorResponse = ApiResponse.error("记录设备控制操作日志失败: " + e.getMessage());
            return gson.toJson(errorResponse);
        }
    }
    
    /**
     * 获取操作日志列表（分页）
     * @param page 页码（从1开始）
     * @param pageSize 每页数量
     * @return JSON格式的日志列表
     */
    @JavascriptInterface
    public String getOperationLogs(int page, int pageSize) {
        try {
            int offset = (page - 1) * pageSize;
            List<OperationLogEntity> logEntities = operationLogDao.getLogsPaginated(offset, pageSize);
            int totalCount = operationLogDao.getLogCount();
            
            // 将实体转换为DTO
            List<OperationLogDto> logDtos = new ArrayList<>();
            for (OperationLogEntity entity : logEntities) {
                OperationLogDto dto = new OperationLogDto();
                dto.setId(entity.getId());
                dto.setUsername(entity.getUsername());
                dto.setOperationType(entity.getOperationType());
                dto.setOperationDescription(entity.getOperationDescription());
                dto.setOperationPage(entity.getOperationPage());
                dto.setOperationTarget(entity.getOperationTarget());
                dto.setOperationStatus(entity.getOperationStatus());
                dto.setErrorMessage(entity.getErrorMessage());
                dto.setOperationTime(entity.getOperationTime());
                dto.setOperationTimeString(entity.getOperationTimeString());
                dto.setIpAddress(entity.getIpAddress());
                logDtos.add(dto);
            }
            
            // 创建分页响应对象
            PageResponseDto<OperationLogDto> pageResponse = new PageResponseDto<>(
                page, pageSize, totalCount, logDtos
            );
            
            // 使用ApiResponse包装分页响应对象
            ApiResponse<PageResponseDto<OperationLogDto>> response = ApiResponse.success("获取操作日志成功", pageResponse);
            
            return gson.toJson(response);
        } catch (Exception e) {
            Log.e(TAG, "获取操作日志失败: " + e.getMessage(), e);
            ApiResponse<String> errorResponse = ApiResponse.error("获取操作日志失败: " + e.getMessage());
            return gson.toJson(errorResponse);
        }
    }
    
    /**
     * 根据用户名获取操作日志
     * @param username 用户名
     * @return JSON格式的日志列表
     */
    @JavascriptInterface
    public String getLogsByUsername(String username) {
        try {
            List<OperationLogEntity> logs = operationLogDao.getLogsByUsername(username);
            return gson.toJson(logs);
        } catch (Exception e) {
            Log.e(TAG, "根据用户名获取操作日志失败: " + e.getMessage(), e);
            Map<String, Object> errorResult = new HashMap<>();
            errorResult.put("error", "获取操作日志失败: " + e.getMessage());
            return gson.toJson(errorResult);
        }
    }
    
    /**
     * 获取所有操作日志
     * @return JSON格式的日志列表
     */
    @JavascriptInterface
    public String getAllOperationLogs() {
        try {
            List<OperationLogEntity> logEntities = operationLogDao.getAllLogs();
            
            // 将实体转换为DTO
            List<OperationLogDto> logDtos = new ArrayList<>();
            for (OperationLogEntity entity : logEntities) {
                OperationLogDto dto = new OperationLogDto();
                dto.setId(entity.getId());
                dto.setUsername(entity.getUsername());
                dto.setOperationType(entity.getOperationType());
                dto.setOperationDescription(entity.getOperationDescription());
                dto.setOperationPage(entity.getOperationPage());
                dto.setOperationTarget(entity.getOperationTarget());
                dto.setOperationStatus(entity.getOperationStatus());
                dto.setErrorMessage(entity.getErrorMessage());
                dto.setOperationTime(entity.getOperationTime());
                dto.setOperationTimeString(entity.getOperationTimeString());
                dto.setIpAddress(entity.getIpAddress());
                logDtos.add(dto);
            }
            
            // 使用ApiResponse返回成功结果
            ApiResponse<List<OperationLogDto>> response = ApiResponse.success("获取所有操作日志成功", logDtos);
            return gson.toJson(response);
        } catch (Exception e) {
            Log.e(TAG, "获取所有操作日志失败: " + e.getMessage(), e);
            // 使用ApiResponse返回错误结果
            ApiResponse<String> errorResponse = ApiResponse.error("获取所有操作日志失败: " + e.getMessage());
            return gson.toJson(errorResponse);
        }
    }
    
    /**
     * 清空操作日志
     * @return 操作结果
     */
    @JavascriptInterface
    public String clearOperationLogs() {
        try {
            int count = operationLogDao.deleteAllLogs();
            
            // 使用ApiResponse返回成功结果
            ApiResponse<Integer> response = ApiResponse.success("操作日志清空成功，共删除 " + count + " 条记录", count);
            return gson.toJson(response);
        } catch (Exception e) {
            Log.e(TAG, "清空操作日志失败: " + e.getMessage(), e);
            // 使用ApiResponse返回错误结果
            ApiResponse<String> errorResponse = ApiResponse.error("清空操作日志失败: " + e.getMessage());
            return gson.toJson(errorResponse);
        }
    }
    
    /**
     * 删除指定天数前的日志
     * @param days 天数
     * @return 操作结果
     */
    @JavascriptInterface
    public String deleteOldLogs(int days) {
        try {
            if (days <= 0) {
                ApiResponse<String> errorResponse = ApiResponse.error("天数必须大于0");
                return gson.toJson(errorResponse);
            }
            
            // 计算截止时间（当前时间减去指定天数）
            long cutoffTime = System.currentTimeMillis() - (days * 24 * 60 * 60 * 1000L);
            int count = operationLogDao.deleteLogsBefore(cutoffTime);
            
            // 使用ApiResponse返回成功结果
            ApiResponse<Integer> response = ApiResponse.success(
                "成功删除 " + days + " 天前的操作日志，共 " + count + " 条记录", count);
            return gson.toJson(response);
        } catch (Exception e) {
            Log.e(TAG, "删除旧操作日志失败: " + e.getMessage(), e);
            // 使用ApiResponse返回错误结果
            ApiResponse<String> errorResponse = ApiResponse.error("删除旧操作日志失败: " + e.getMessage());
            return gson.toJson(errorResponse);
        }
    }
    
    /**
     * 获取操作日志统计信息
     * @return JSON格式的统计信息
     */
    @JavascriptInterface
    public String getOperationLogStats() {
        try {
            long todayStart = getTodayStartTime();
            int totalCount = operationLogDao.getLogCount();
            int todayCount = operationLogDao.getLogCountSince(todayStart);
            int successCount = operationLogDao.getLogCountByStatus(OperationLogEntity.OperationStatus.SUCCESS);
            int failedCount = operationLogDao.getLogCountByStatus(OperationLogEntity.OperationStatus.FAILED);
            
            Map<String, Object> stats = new HashMap<>();
            stats.put("totalCount", totalCount);
            stats.put("todayCount", todayCount);
            stats.put("successCount", successCount);
            stats.put("failedCount", failedCount);
            
            // 使用ApiResponse返回成功结果
            ApiResponse<Map<String, Object>> response = ApiResponse.success("获取操作日志统计信息成功", stats);
            return gson.toJson(response);
        } catch (Exception e) {
            Log.e(TAG, "获取操作日志统计信息失败: " + e.getMessage(), e);
            // 使用ApiResponse返回错误结果
            ApiResponse<String> errorResponse = ApiResponse.error("获取操作日志统计信息失败: " + e.getMessage());
            return gson.toJson(errorResponse);
        }
    }
    
    /**
     * 获取今天开始的时间戳
     */
    private long getTodayStartTime() {
        Date today = new Date();
        today.setHours(0);
        today.setMinutes(0);
        today.setSeconds(0);
        return today.getTime();
    }
    
    /**
     * 释放资源
     */
    public void release() {
        if (executor != null && !executor.isShutdown()) {
            executor.shutdown();
        }
    }
} 